//------------------------------------------------------------------------------
//  RenderApplication.cpp
//  (C) 2009 xoyojank
//------------------------------------------------------------------------------
#include "StdEddy.h"
#include "Application/RenderApplication.h"
#include "Common/FileSystem.h"


//------------------------------------------------------------------------------
namespace Eddy
{

//------------------------------------------------------------------------------
RenderApplication::RenderApplication()
    : isOpen(false)
    , appName(L"Eddy Render Application")
    , time(0)
    , frameTime(0)
    , isQuit(false)
    , displayDevice(NULL)
    , renderDevice(NULL)
    , effectManager(NULL)
{
}

//------------------------------------------------------------------------------
RenderApplication::~RenderApplication()
{
    assert(this->IsOpen());
}


//------------------------------------------------------------------------------
bool
RenderApplication::Open()
{
    assert(!this->IsOpen());

    // create
    this->displayDevice = DisplayDevice::Create();
    this->renderDevice = RenderDevice::Create();
    this->effectManager = EffectManager::Create();
    this->displayDevice->SetWindowTitle(this->GetAppName());
    // open
    if (!this->displayDevice->Open())
        return false;
    if (!this->renderDevice->Open())
        return false;
    if (!this->effectManager->Open())
        return false;

    this->renderDevice->SetClearColor(float4(0, 0, 1, 1));
    this->isOpen = true;

    return this->isOpen;
}

//------------------------------------------------------------------------------
void
RenderApplication::Close()
{
    assert(this->IsOpen());

    EffectManager::Destroy();
    this->effectManager = NULL;
    RenderDevice::Destroy();
    this->renderDevice = NULL;
    DisplayDevice::Destroy();
    this->displayDevice = NULL;

    this->isOpen = false;
}

//------------------------------------------------------------------------------
void
RenderApplication::Run()
{
    assert(this->IsOpen());

    while (!this->isQuit)
    {
        this->displayDevice->ProcessWindowMessage();
        this->OnProcessInput();
        this->UpdateTime();
        this->OnUpdateFrame();
        this->OnRenderFrame();

        Sleep(0);
    }
}

//------------------------------------------------------------------------------
void
RenderApplication::UpdateTime()
{
    __int64 counter;
    QueryPerformanceCounter((LARGE_INTEGER*)&counter);
    double curTime = double(counter) * 0.001;
    this->frameTime = curTime - this->time;
    this->time = curTime;
}

//------------------------------------------------------------------------------
void
RenderApplication::OnProcessInput()
{
    // override in sub class
}

//------------------------------------------------------------------------------
void
RenderApplication::OnUpdateFrame()
{
    // override in sub class
}

//------------------------------------------------------------------------------
void
RenderApplication::OnRenderFrame()
{
    this->renderDevice->Clear();
    this->renderDevice->Present();
}

}// Eddy